import { Component, ElementRef, OnInit, ViewEncapsulation } from '@angular/core';
import { ControlUIWidget } from '@delon/form';
import { BehaviorSubject, debounceTime, switchMap, takeUntil } from 'rxjs';

import { SFStringWidgetSchema } from './schema';

@Component({
    selector: 'sf-password',
    templateUrl: './password.widget.html',
    preserveWhitespaces: false,
    encapsulation: ViewEncapsulation.None
})
export class PasswordWidget extends ControlUIWidget<SFStringWidgetSchema> implements OnInit {
    static readonly KEY = 'password';

    showPasswordFlag: boolean = false;

    type: string = 'addon';
    private change$: BehaviorSubject<string> | null = null;

    ngOnInit(): void {
        const { autofocus } = this.ui;
        if (autofocus === true) {
            setTimeout(() => {
                ((this.injector.get(ElementRef).nativeElement as HTMLElement).querySelector(`#${this.id}`) as HTMLElement).focus();
            }, 20);
        }
        this.initChange();
    }

    private initChange(): void {
        const dueTime = this.ui.changeDebounceTime;
        const changeFn = this.ui.change;
        if (dueTime == null || dueTime <= 0 || changeFn == null) return;

        this.change$ = new BehaviorSubject<string>(this.value);
        let obs = this.change$.asObservable().pipe(debounceTime(dueTime), takeUntil(this.sfItemComp!.destroy$));
        if (this.ui.changeMap != null) {
            obs = obs.pipe(switchMap(this.ui.changeMap));
        }
        obs.subscribe(val => changeFn(val));
    }

    change(val: string): void {
        this.setValue(val);
        if (this.change$ != null) {
            this.change$.next(val);
            return;
        }
        if (this.ui.change) this.ui.change(val);
    }

    /**
     * 展示密码
     */
    taggerShowPassword() {
        this.showPasswordFlag = !this.showPasswordFlag;
    }

    focus(e: FocusEvent): void {
        if (this.ui.focus) this.ui.focus(e);
    }

    blur(e: FocusEvent): void {
        if (this.ui.blur) this.ui.blur(e);
    }

    enter(e: Event): void {
        if (this.ui.enter) this.ui.enter(e);
    }
}
